import { keywordCompare } from '@gnlab/utils'
import services from '@/services'
import type { BaseAccount } from '@/services/auth'
import type { AccountQywx } from '@/services/qywxs'

/**
 * 返回选择企业微信所需的数据
 */
export type AccountForChoose = Pick<BaseAccount, 'id' | 'name' | 'remark'>
export type QywxForChoose = Pick<
  AccountQywx,
  'wxid' | 'accountId' | 'avatar' | 'friendlyName' | 'friendlyFullName' | 'corpname'
>
export interface ChoosingData<Q extends QywxForChoose = QywxForChoose> {
  accounts: AccountForChoose[]
  qywxs: Q[]
}

export function useChoosingData<Q extends QywxForChoose = QywxForChoose>(params: {
  inputData?: ChoosingData<Q> // 使用者自行提供数据
  onlineOnly?: boolean // true: 只获取在线的微信；false：包含离线的微信。默认为 true，有 inputData 时无效
}) {
  const { inputData, onlineOnly = true } = params

  // 获取数据
  const [data, setData] = useState(inputData)
  useEffect(() => {
    if (data) return
    void services.qywxs.getAllAccountQywxs(onlineOnly).then(data => {
      setData(data as unknown as ChoosingData<Q>)
    })
  }, [data, onlineOnly])

  // 过滤数据
  const qywxs = data?.qywxs

  const [conditions, setConditions] = useState({ keyword: '', accountId: '' })
  function updateConditions(updates: Partial<typeof conditions>) {
    setConditions(conditions => ({ ...conditions, ...updates }))
  }

  const filteredQywxs = useMemo(() => {
    if (!qywxs) return undefined

    const keyword = conditions.keyword.trim()
    return qywxs.filter(qywx => {
      if (keyword && !keywordCompare(keyword, qywx.friendlyFullName)) return false
      if (conditions.accountId && qywx.accountId !== conditions.accountId) return false
      return true
    })
  }, [qywxs, conditions])

  return {
    conditions,
    updateConditions,
    accounts: data?.accounts,
    qywxs,
    filteredQywxs,
  }
}

/**
 * 处理选中状态
 */
export function useChoose(params: {
  qywxs: QywxForChoose[] | undefined // 待选择的企业微信列表
  disabledWxids?: Set<string> // 不允许选中的 wxid 列表
  choosed: string[] // 当前选中的 wxid 列表
  setChoosed: (wxids: string[]) => void // 更新选中的列表
}) {
  const { qywxs, disabledWxids, choosed, setChoosed } = params

  // 若发现 choosed 里有不允许选中的 wxid，把有效的列表同步给使用者
  // 此行为必须在 effect 里进行，因为下级组件渲染过程中，不允许直接触发上级组件的 setState
  useEffect(() => {
    const validChoosed = choosed.filter(
      wxid =>
        (!qywxs || !!qywxs.find(qywx => qywx.wxid === wxid)) && disabledWxids?.has(wxid) !== true,
    )
    if (validChoosed.length !== choosed.length) {
      setChoosed(validChoosed)
    }
  }, [qywxs, disabledWxids, choosed, setChoosed])

  // 切换指定 wxid 的选中状态
  function switchChoose(wxid: string) {
    const updated = choosed.includes(wxid)
      ? choosed.filter(_wxid => _wxid !== wxid)
      : [...choosed, wxid]
    setChoosed(updated)
  }

  return { switchChoose }
}
